package ph.com.gs3.chat.managers;

import java.util.ArrayList;
import java.util.List;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import ph.com.gs3.chat.communicators.HttpCommunicatorModule.CommunicatorException;
import ph.com.gs3.chat.communicators.UserCommunicatorModule;
import ph.com.gs3.chat.model.valueobject.application.APIResponse;
import ph.com.gs3.chat.model.valueobject.application.APIResponse.APIInvalidResponseException;
import ph.com.gs3.chat.model.valueobject.application.APIResponse.APIStatus;
import ph.com.gs3.chat.model.valueobject.business.User;
import ph.com.gs3.chat.model.valueobject.business.UserStub;
import ph.com.gs3.chat.utilities.FLLogger;

public class UserManager {

	public static final String TAG = UserManager.class.getSimpleName();

	private UserCommunicatorModule userCommunicatorModule;

	public UserManager(UserCommunicatorModule userCommunicatorModule) {

		this.userCommunicatorModule = userCommunicatorModule;

	}

	public List<UserStub> getOnlineUsers(User currentUser) throws UserDownloadFailedException,
	        UserParseException {

		List<UserStub> onlineUsers = new ArrayList<>();

		String result = "";

		try {
			APIResponse response = userCommunicatorModule.getOnlineUsers(currentUser);

			if (response.getStatus() == APIStatus.SUCCESS) {

				result = response.getResults();
				// throws JSONException
				JSONArray onlineUsersRaw = new JSONArray(result);

				int onlineUserCount = onlineUsersRaw.length();

				for (int i = 0; i < onlineUserCount; i++) {
					String rawUserStubString = onlineUsersRaw.getString(i);
					try {
						JSONObject rawUserStub = new JSONObject(rawUserStubString);
						UserStub userStub = UserStub.createFromJSON(rawUserStub);
						onlineUsers.add(userStub);
					} catch (JSONException e) {
						FLLogger.w(TAG, "Unable to parse user stub: " + rawUserStubString);
					}

				}

			} else {
				throw new UserDownloadFailedException(response.getErrorMessage());
			}

		} catch (CommunicatorException | APIInvalidResponseException e) {
			throw new UserDownloadFailedException(e);
		} catch (JSONException e) {
			throw new UserParseException("Unable to parse user using json array: " + result);
		}

		return onlineUsers;
	}

	// ==========================================================================
	// {{ Exceptions

	public static class UserDownloadFailedException extends Exception {

		private static final long serialVersionUID = -7365755767052581878L;

		public UserDownloadFailedException(String message) {
			super(message);
		}

		public UserDownloadFailedException(Throwable throwable) {
			super(throwable);
		}

		public UserDownloadFailedException(Throwable throwable, String message) {
			super(message, throwable);
		}

	}

	public static class UserParseException extends Exception {

		private static final long serialVersionUID = -949784711114280051L;

		public UserParseException(String message) {
			super(message);
		}

	}

	// }}

}
